package com.dms.modules.product.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.dms.modules.product.entity.Product;
import com.dms.modules.product.entity.ProductCategory;
import com.dms.modules.product.mapper.ProductCategoryMapper;
import com.dms.modules.product.service.ProductCategoryService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * 商品分类服务实现类
 */
@Slf4j
@Service
public class ProductCategoryServiceImpl extends ServiceImpl<ProductCategoryMapper, ProductCategory> implements ProductCategoryService {

    @Override
    public List<ProductCategory> getCategoryTree() {
        List<ProductCategory> allCategories = this.list();
        return buildCategoryTree(allCategories);
    }

    @Override
    public Page<ProductCategory> pageCategories(Integer pageNum, Integer pageSize, String name) {
        Page<ProductCategory> page = new Page<>(pageNum, pageSize);
        LambdaQueryWrapper<ProductCategory> wrapper = new LambdaQueryWrapper<>();
        
        if (StringUtils.isNotBlank(name)) {
            wrapper.like(ProductCategory::getName, name);
        }
        
        wrapper.orderByAsc(ProductCategory::getSort);
        return this.page(page, wrapper);
    }

    @Override
    public boolean hasProducts(Long categoryId) {
        Integer count = baseMapper.countProductsByCategory(categoryId);
        return count != null && count > 0;
    }

    @Override
    public void updateVisible(Long categoryId, Integer visible) {
        LambdaUpdateWrapper<ProductCategory> wrapper = new LambdaUpdateWrapper<>();
        wrapper.eq(ProductCategory::getId, categoryId)
                .set(ProductCategory::getVisible, visible);
        this.update(wrapper);
    }

    @Override
    public List<ProductCategory> getCategoriesByDimension(String dimension) {
        LambdaQueryWrapper<ProductCategory> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(ProductCategory::getDimension, dimension);
        return this.list(wrapper);
    }

    @Override
    public List<ProductCategory> getCategoryList(Long parentId) {
        LambdaQueryWrapper<ProductCategory> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(parentId != null, ProductCategory::getParentId, parentId)
                .orderByAsc(ProductCategory::getSort);
        return this.list(wrapper);
    }

    @Override
    public List<ProductCategory> getDimensionCategories(String dimension) {
        return this.getCategoriesByDimension(dimension);
    }

    @Override
    public IPage<Product> getCategoryProducts(Long categoryId, Integer pageNum, Integer pageSize) {
        Page<Product> page = new Page<>(pageNum, pageSize);
        return baseMapper.selectCategoryProducts(page, categoryId);
    }

    @Override
    public IPage<Product> getFilteredCategoryProducts(List<Long> categoryIds, Integer pageNum, Integer pageSize) {
        Page<Product> page = new Page<>(pageNum, pageSize);
        return baseMapper.selectFilteredCategoryProducts(page, categoryIds);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public Long addCategory(ProductCategory category) {
        this.save(category);
        return category.getId();
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean updateCategory(ProductCategory category) {
        return this.updateById(category);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean deleteCategory(Long id) {
        // 检查是否有子分类
        List<ProductCategory> children = getChildren(id);
        if (!children.isEmpty()) {
            throw new RuntimeException("该分类下存在子分类，无法删除");
        }
        return this.removeById(id);
    }

    @Override
    public ProductCategory getCategory(Long id) {
        return this.getById(id);
    }

    @Override
    public List<ProductCategory> getChildren(Long parentId) {
        LambdaQueryWrapper<ProductCategory> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(ProductCategory::getParentId, parentId);
        return this.list(wrapper);
    }

    @Override
    public List<ProductCategory> buildCategoryTree(List<ProductCategory> categories) {
        List<ProductCategory> tree = new ArrayList<>();
        
        // 使用 Map 优化查找效率
        Map<Long, ProductCategory> categoryMap = categories.stream()
            .collect(Collectors.toMap(ProductCategory::getId, category -> category));
            
        for (ProductCategory category : categories) {
            Long parentId = category.getParentId();
            if (parentId == null || parentId == 0) {
                // 根节点
                tree.add(category);
            } else {
                // 将当前节点添加到父节点的 children 集合中
                ProductCategory parent = categoryMap.get(parentId);
                if (parent != null) {
                    if (parent.getChildren() == null) {
                        parent.setChildren(new ArrayList<>());
                    }
                    parent.getChildren().add(category);
                }
            }
        }
        return tree;
    }
} 